package com.zhangfb95.crosschain.plugin.container.java.fabric2.service;

import org.hyperledger.fabric.sdk.BlockEvent;
import org.hyperledger.fabric.sdk.BlockInfo;
import org.hyperledger.fabric.sdk.Channel;
import org.hyperledger.fabric.sdk.TransactionInfo;
import org.hyperledger.fabric.sdk.exception.InvalidArgumentException;
import org.hyperledger.fabric.sdk.exception.ProposalException;

import java.util.Map;
import java.util.Set;

/**
 * @author zhangfubing
 * @since 2023/7/6
 */
public interface FabricService {

    /**
     * 构建通道对象
     *
     * @param channelName 通道名称
     * @return 通道对象
     */
    Channel buildChannel(String channelName);

    /**
     * 获取区块高度
     *
     * @param channelName 通道名称
     * @return 区块高度
     */
    long getHeight(String channelName);

    /**
     * 根据区块编号查询区块
     *
     * @param channelName 通道名称
     * @param blockNumber 区块编号
     * @return 区块信息
     */
    BlockInfo queryBlockByNumber(String channelName, long blockNumber);

    /**
     * 根据区块哈希查询区块
     *
     * @param channelName 通道名称
     * @param blockHash   区块哈希
     * @return 区块信息
     */
    BlockInfo queryBlockByHash(String channelName, String blockHash);

    /**
     * 根据交易ID查询交易信息
     *
     * @param channelName 通道名称
     * @param txID        交易ID
     * @return 交易信息
     */
    TransactionInfo queryTransactionByID(String channelName, String txID);

    /**
     * 查询安装的链码列表
     *
     * @param channelName 通道名称
     * @return 链码列表
     */
    Map<String, Map<String, String>> queryInstalledChainCodes(String channelName);

    /**
     * 查询安装的链码列表
     *
     * @param channelName 通道名称
     * @param mspId       mspId
     * @return 链码列表
     */
    Map<String, Map<String, String>> queryInstalledChainCodes(String channelName, String mspId);

    /**
     * 发送交易
     *
     * @param serverId      服务id
     * @param userId        用户id
     * @param chainPath     链路径
     * @param channelName   通道名称
     * @param chaincodeName 链码名称
     * @param fcn           方法名称
     * @param args          参数列表
     * @return 区块交易事件信息
     */
    BlockEvent.TransactionEvent sendTransaction(String serverId,
                                                Long userId,
                                                String chainPath,
                                                String channelName,
                                                String chaincodeName,
                                                String fcn,
                                                String[] args);

    /**
     * 查询链码
     *
     * @param serverId      服务id
     * @param userId        用户id
     * @param chainPath     链路径
     * @param channelName   通道名称
     * @param chaincodeName 链码名称
     * @param fcn           方法名称
     * @param args          参数列表
     * @return 查询结果
     */
    String queryByChaincode(String serverId,
                            Long userId,
                            String chainPath,
                            String channelName,
                            String chaincodeName,
                            String fcn,
                            String[] args);

    /**
     * 查询通道列表
     *
     * @return 通道列表
     * @throws ProposalException        提案异常
     * @throws InvalidArgumentException 无效参数异常
     */
    Set<String> queryChannels() throws ProposalException, InvalidArgumentException;

    /**
     * 计算区块哈希
     *
     * @param blockInfo 区块信息
     * @return 区块哈希
     */
    byte[] calculateBlockHash(BlockInfo blockInfo);
}
